/**
 *
 */
package ua.at.tsvetkov.samizdat.activities;

import ua.at.tsvetkov.application.AppConfig;
import ua.at.tsvetkov.samizdat.Const;
import ua.at.tsvetkov.samizdat.Key;
import ua.at.tsvetkov.samizdat.R;
import ua.at.tsvetkov.samizdat.adapters.AdtBookColors;
import ua.at.tsvetkov.samizdat.data.AllBooksDownloader;
import ua.at.tsvetkov.samizdat.data.Book;
import ua.at.tsvetkov.samizdat.data.BookColor;
import ua.at.tsvetkov.samizdat.data.BookDownloader;
import ua.at.tsvetkov.samizdat.data.FavoriteAuthors;
import ua.at.tsvetkov.samizdat.data.FavoriteBooks;
import ua.at.tsvetkov.samizdat.data.OnCompleteLoadListener;
import ua.at.tsvetkov.samizdat.data.ReadedBooksData;
import ua.at.tsvetkov.ui.Rout;
import ua.at.tsvetkov.util.Log;
import android.app.AlertDialog;
import android.app.Dialog;
import android.app.ProgressDialog;
import android.content.DialogInterface;
import android.os.Bundle;
import android.view.KeyEvent;
import android.view.Menu;
import android.view.MenuItem;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.View.OnTouchListener;
import android.widget.ScrollView;
import android.widget.SeekBar;
import android.widget.SeekBar.OnSeekBarChangeListener;
import android.widget.TextView;
import android.widget.Toast;
import android.widget.ZoomControls;

/**
 * @author A.Tsvetkov 2011, http://tsvetkov.at.ua, al@ukr.net
 */
public class AcBook_ extends AcTemplate {

	private static final int	MENU_DELETE						= 4;
	private static final int	MENU_BOOK_COLORS				= 3;
	private static final int	MENU_LOAD_ALL_AUTHR_BOOKS	= 2;
	private static final int	MENU_FAVORITES_AUTHORS		= 1;
	private static final int	MENU_FAVORITS					= 0;

	private static final int	DIALOG_COLOR_SELECT			= 1;
	private static final int	DIALOG_LOW_MEMORY				= 2;

	private BookDownloader		bookDownloader;
	private FavoriteAuthors		favoriteAuthors;
	private FavoriteBooks		favoriteBooks;
	private ReadedBooksData		readedBooksData;
	private ScrollView			scrollView;
	private TextView				title;
	private TextView				author;
	private TextView				pages;
	private TextView				content;
	private ZoomControls			zoomControl;
	private SeekBar				seekBarContent;
	private float					textSize;
	private int						percent;
	private int						height;
	private int						pageSize;
	private int						contentHeight;
	private Book					book;
	private int						bookColorsSet;
	private long					memorySize;
	private String					authorUrl;
//	private String[]				bookData;
	private StringBuilder		data;

	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		try {
			book = new Book(AppConfig.getString(Key.CURRENT_BOOK));
			Log.v(book.toString());
		} catch (Exception e) {
			Log.e(e);
			Toast.makeText(this, "Ошибка на сервере.\nНе могу получить данные по книге.", Toast.LENGTH_LONG);
			finish();
		}
		addTextView();
		textInfo.setVisibility(View.VISIBLE);
		favoriteAuthors = new FavoriteAuthors(this);
		favoriteBooks = new FavoriteBooks(this);
		readedBooksData = new ReadedBooksData();
		content = (TextView) findViewById(R.id.AcBookText);
		textSize = AppConfig.getFloat(Key.TEXT_SIZE, Const.DEFAULT_TEXT_SIZE);
		content.setText("");
		System.gc();
		content.setTextSize(textSize);
		content.setVerticalScrollBarEnabled(true);
		bookColorsSet = AppConfig.getInt(Key.BOOK_COLORS_SET, 0);
		content.setBackgroundResource(BookColor.colors[bookColorsSet].background);
		content.setTextColor(BookColor.colors[bookColorsSet].textColor);
		scrollView = (ScrollView) findViewById(R.id.AcBookScrollView);
		zoomControl = (ZoomControls) findViewById(R.id.AcBookZoomControls);
		zoomControl.setVisibility(View.INVISIBLE);
		seekBarContent = (SeekBar) findViewById(R.id.AcBookSeekBar);
		seekBarContent.setVisibility(View.INVISIBLE);
		author = (TextView) findViewById(R.id.AcTemplateTitle);
		author.setText(book.author);
		title = (TextView) findViewById(R.id.AcTemplateInfo);
		title.setText(book.title);
		pages = (TextView) findViewById(R.id.AcTemplatePages);
		pages.setText("0%");
		scrollView.setOnTouchListener(getScrollViewTouchListener());
		seekBarContent.setOnSeekBarChangeListener(getSeekBarListener());

		zoomControl.setOnZoomInClickListener(new OnClickListener() {

			public void onClick(View v) {
				makeZoom(1);
			}

		});

		zoomControl.setOnZoomOutClickListener(new OnClickListener() {

			public void onClick(View v) {
				makeZoom(-1);
			}

		});
	}

	/*
	 * (non-Javadoc)
	 * @see ua.at.tsvetkov.debug.AcSimpleTrackingActivity#onLowMemory()
	 */
	@Override
	public void onLowMemory() {
		super.onLowMemory();
	}

	private void loadSettings() {
		favoriteAuthors.load();
		favoriteBooks.load();
		readedBooksData.load();
		readedBooksData.getBookData(book);
		Log.v("After " + book);
	}

	private void saveSettings() {
		book.position = scrollView.getScrollY();
		readedBooksData.putBook(book);
		Log.v("Current " + book);
		readedBooksData.save();
		favoriteAuthors.save();
		favoriteBooks.save();
	}

	@Override
	public boolean onPrepareOptionsMenu(Menu menu) {
		menu.clear();
		menu.add(0, MENU_FAVORITS, 0, "Избранное").setIcon(R.drawable.ic_opt_favorite);
		menu.add(0, MENU_FAVORITES_AUTHORS, 0, "Избранные авторы").setIcon(R.drawable.ic_opt_favorite_author);
		menu.add(0, MENU_LOAD_ALL_AUTHR_BOOKS, 0, "Загрузить книги автора").setIcon(R.drawable.ic_opt_load);
		menu.add(0, MENU_BOOK_COLORS, 0, "Цвет текста").setIcon(R.drawable.ic_opt_text_colors);
		menu.add(0, MENU_DELETE, 0, "Удалить").setIcon(android.R.drawable.ic_delete);
		return super.onCreateOptionsMenu(menu);
	}

	@Override
	public void onStop() {
		saveSettings();
		bookDownloader = null;
		content = null;
		System.gc();
		super.onStop();
	}

	/*
	 * (non-Javadoc)
	 * @see ua.at.tsvetkov.debug.AcSimpleTrackingActivity#onResume()
	 */
	@Override
	protected void onResume() {
		loadSettings();
		downloadBook();
		super.onResume();
	}

	/**
	 * 
	 */
	private void downloadBook() {
		data = null;
		bookDownloader = null;
		data = new StringBuilder();
		bookDownloader = new BookDownloader(this, book, (ProgressDialog) onCreateDialog(AcTemplate.DIALOG_LOAD));
		new Thread(new Runnable() {

			@Override
			public void run() {
				bookDownloader.download(true, false);
//				bookDownloader.loadNextPage();
				authorUrl = bookDownloader.getAuthorUrl();
//				bookData = bookDownloader.getHeader();
				Log.v("Book size = " + data.length() * 2 / 1024 + "Kb");
				runOnUiThread(new Runnable() {

					@Override
					public void run() {
						content.setText(data.toString());
					}
				});
				scrollView.post(new Runnable() {
					@Override
					public void run() {
						scrollView.scrollTo(0, book.position);
						bookDownloader = null;
						System.gc();
					}
				});
			}

		}).start();
	}

	/**
	 * Options menu handler
	 */
	@Override
	public boolean onOptionsItemSelected(MenuItem item) {
		switch (item.getItemId()) {
			case MENU_FAVORITS: {
				favoriteBooks.setFavorite(book);
				break;
			}
			case MENU_FAVORITES_AUTHORS: {
				favoriteAuthors.setFavoriteAuthor(book);
				break;
			}
			case MENU_LOAD_ALL_AUTHR_BOOKS: {
				loadAllAuthorBooks();
				break;
			}
			case MENU_BOOK_COLORS: {
				shoceColors();
				break;
			}
			case MENU_DELETE: {
				book.delete();
				AppConfig.putSetting(Key.CURRENT_BOOK, "");
				finish();
				break;
			}
		}
		return false;
	}

	/**
	 * Загрузить все книги данного автора
	 */
	private void loadAllAuthorBooks() {
		AllBooksDownloader allBooksDownloader = new AllBooksDownloader(this, (ProgressDialog) onCreateDialog(DIALOG_LOAD), authorUrl);
		allBooksDownloader.setOnCompleteLoadListener(new OnCompleteLoadListener() {

			@Override
			public void loadComplete(boolean isLoaded) {
				if (isLoaded) {
					Rout.toast(AcBook_.this, "Загрузка книг автора завершена успешно.", Toast.LENGTH_LONG);
				} else {
					Rout.toast(AcBook_.this, "Загрузка книг автора завершена с ошибками.", Toast.LENGTH_LONG);
				}
			}

		});
		allBooksDownloader.download();
	}

	private void shoceColors() {
		showDialog(DIALOG_COLOR_SELECT);
	}

	/**
	 * Возвращает листенер SeekBar
	 * 
	 * @return
	 */
	private OnSeekBarChangeListener getSeekBarListener() {
		return new OnSeekBarChangeListener() {

			public void onProgressChanged(SeekBar seekBar, int pr, boolean fromUser) {
				seekBarContent.setProgress(pr);
				scrollView.scrollTo(0, pr * content.getHeight() / 100);
				setCurrentPositionText();
			}

			public void onStartTrackingTouch(SeekBar seekBar) {
			}

			public void onStopTrackingTouch(SeekBar seekBar) {
			}

		};
	}

	/**
	 * Возвращает листенер касания прокрутки
	 * 
	 * @return
	 */
	private OnTouchListener getScrollViewTouchListener() {
		return new OnTouchListener() {

			public boolean onTouch(View v, MotionEvent event) {
				setCurrentPositionText();
				if (event.getAction() == MotionEvent.ACTION_UP && event.getEventTime() - event.getDownTime() < 200) {
					float y = event.getY();
					if (y > height * 0.7) {
						paging(true);
					} else if (y < height * 0.3) {
						paging(false);
					} else {
						if (zoomControl.getVisibility() == View.INVISIBLE) {
							zoomControl.setVisibility(View.VISIBLE);
							seekBarContent.setVisibility(View.VISIBLE);
							seekBarContent.setProgress(percent);
						} else {
							zoomControl.setVisibility(View.INVISIBLE);
							seekBarContent.setVisibility(View.INVISIBLE);
						}
					}
				}
				return false;
			}

		};
	}

	/**
	 * Листание страниц
	 * 
	 * @param next true - вперед false - назад
	 */
	private void paging(boolean next) {
		if (next) {
			scrollView.scrollTo(0, scrollView.getScrollY() + pageSize);
		} else {
			scrollView.scrollTo(0, scrollView.getScrollY() - pageSize);
		}
	}

	/**
	 * Увеличение текста
	 * 
	 * @param dif разница увеличения
	 */
	private void makeZoom(float dif) {
		textSize = textSize + dif;
		content.setTextSize(textSize);
		content.postInvalidate();
		setCurrentPositionText();
		AppConfig.putSetting(Key.TEXT_SIZE, textSize, AppConfig.SAVE);
	}

	/**
	 *
	 */
	private void setCurrentPositionText() {
		pages.setText((int) (100 * scrollView.getScrollY() / contentHeight) + "%");
	}

	/*
	 * (non-Javadoc)
	 * @see android.app.Activity#onWindowFocusChanged(boolean)
	 */
	@Override
	public void onWindowFocusChanged(boolean hasFocus) {
		textSize = AppConfig.getFloat(Key.TEXT_SIZE, Const.DEFAULT_TEXT_SIZE);
		content.setTextSize(textSize);
		height = scrollView.getHeight();
		contentHeight = content.getHeight();
		pageSize = height - 20;
		setCurrentPositionText();
		super.onWindowFocusChanged(hasFocus);
	}

	@Override
	public boolean dispatchKeyEvent(KeyEvent event) {
		int action = event.getAction();
		int keyCode = event.getKeyCode();
		switch (keyCode) {
			case KeyEvent.KEYCODE_VOLUME_UP:
				if (action == KeyEvent.ACTION_DOWN) {
					paging(false);
				}
				return true;
			case KeyEvent.KEYCODE_VOLUME_DOWN:
				if (action == KeyEvent.ACTION_DOWN) {
					paging(true);
				}
				return true;
			default:
				return super.dispatchKeyEvent(event);
		}
	}

	/*
	 * (non-Javadoc)
	 * @see ua.at.tsvetkov.samizdat.activities.AcTemplate#onCreateDialog(int)
	 */
	@Override
	public Dialog onCreateDialog(int id) {
		switch (id) {
			case DIALOG_COLOR_SELECT: {
				AlertDialog.Builder builder = new AlertDialog.Builder(this);
				builder.setTitle("Выбор цветов для чтения");
				AdtBookColors adt = new AdtBookColors(this);
				builder.setAdapter(adt, new DialogInterface.OnClickListener() {

					@Override
					public void onClick(DialogInterface dialog, final int position) {
						content.post(new Runnable() {
							@Override
							public void run() {
								content.setBackgroundResource(BookColor.colors[position].background);
								content.setTextColor(BookColor.colors[position].textColor);
								AppConfig.putSetting(Key.BOOK_COLORS_SET, position, AppConfig.SAVE);
							}
						});
					}

				});

				return builder.create();
			}
			case DIALOG_LOW_MEMORY: {
				AlertDialog.Builder builder = new AlertDialog.Builder(this);
				builder.setTitle("Мало памяти.");
				builder.setMessage("К сожалению не хватает памяти для загрузки произведения.\nЕсть " + memorySize / 1024 + "Kb а нужно " + book.getFileSize() / 1024
						+ "Kb\nПопробуйте очистить память Вашего устройства и запустите снова.");
				builder.setPositiveButton("Ok", new DialogInterface.OnClickListener() {

					@Override
					public void onClick(DialogInterface dialog, int which) {
						finish();
					}

				});
				return builder.create();
			}
		}
		return super.onCreateDialog(id);
	}

}
